<template>
	<el-tree
		ref="tree"
		v-loading="loading"
		:data="list"
		:props="defaultProps"
		:lazy="true"
		:load="getProxyChildList"
		:node-key="'userName'"
		:default-expanded-keys="expandedKeys"
		:expand-on-click-node="false"
		:auto-expand-parent="false"
		:indent="0"
		@node-expand="nodeExpend"
		@node-collapse="nodeCollapse"
		class="proxy-tree"
		:isLeaf="true"
		
	>
		<div class="custom-tree-node" slot-scope="{ node, data }">
			<div
				class="node-label tree-item"
				:class="data.userName"
				@click.stop="nodeClick(data, 1)"
			>
				<!-- <span>{{ data.proxyLevel }}/{{ data.proxyLevelName }}</span>
				<span style="margin-left: 1px; margin-right: 1px">·</span> -->
				<span>{{ data.userName }}</span>
				<span style="margin-left: 1px">
					({{ data.directlyUnderProxyNum }}/{{ data.underProxyNum }})
				</span>
			</div>
			<div v-if="showMember" class="member-expand">
				<i
					class="el-icon"
					:class="
						proxyChilds[data.userName] &&
						proxyChilds[data.userName].memberList &&
						proxyChilds[data.userName].memberList.expand
							? 'el-icon-minus'
							: 'el-icon-plus'
					"
					:title="$t('直属会员')"
					@click.stop="toggleMember(node)"
				></i>
				<div
					v-if="
						proxyChilds[data.userName] &&
							proxyChilds[data.userName].memberList
					"
					class="member-tree"
					:class="
						proxyChilds[data.userName] &&
						proxyChilds[data.userName].memberList.expand
							? 'toggin-show'
							: 'toggin-hide'
					"
					:loading="
						proxyChilds[data.userName] &&
							proxyChilds[data.userName].memberList.loading
					"
				>
					<div
						class="member-item tree-item"
						v-for="(item, index) in proxyChilds[data.userName]
							.memberList.data"
						:class="item.userName"
						:key="index"
						@click.stop="nodeClick(item, 2)"
					>
						{{ item.userName }}
					</div>
				</div>
			</div>
		</div>
	</el-tree>
</template>
<script>
import { mapGetters } from 'vuex'

export default {
	props: {
		showMember: {
			type: Boolean,
			default: true
		},
		showProxy: {
			type: Boolean,
			default: true
		},
		selectedData: {
			// 选中的数据. type: 1.代理  2.会员   userName.代理/会员名称
			type: Object,
			default: {}
		},
		detailData: {
			type: Object,
			default: {}
		},
		createdAtStart: {
			type: String,
			default: ''
		},
		createdAtEnd: {
			type: String,
			default: ''
		},
		commissionModel: {
			type: Number,
			default: 1
		}
	},
	data() {
		return {
			defaultProps: {
				children: 'childList',
				label: 'userName',
				isLeaf: (data, node) => {
					if (!data?.underProxyNum) {
						return true
					}
				}
			},
			list: [],
			loading: false,
			expandedKeys: [], // 默认展开的数据
			proxyChilds: {}, // 代理下级列表
			currentNodeData: {} // 当前待选中节点
		}
	},
	computed: {
		...mapGetters(['userInfo'])
	},
	created() {
		this._proxyLevelLink()
	},
	methods: {
		reset() {
			this.currentNodeData = {}
			this.expandedKeys = []
			this.list = []
			this.proxyChilds = {}
			this._proxyLevelLink()
		},
		beforeClose() {
			this.$emit('update:visible', false)
		},
		_proxyLevelLink() {
			this.loading = true
			const func = 'proxyLevelLink'
			const data = {
				id: this.detailData.proxyId,
				merchantId: this.detailData.merchantId,
				reportDate: this.detailData.reportDate
			}
			data.createdAtStart = this.createdAtStart || undefined
			data.createdAtEnd = this.createdAtEnd || undefined
			const that = this
			this.list = []
			that.$api[func](data)
				.then(async (res) => {
					that.loading = false
					if (res.data) {
						if (this.commissionModel === 2) {
							that.list = [{
								...res.data,
								childList: [],
							}]
						} else {
							that.list = [res.data]
						}
					
						that.expandedKeys = [that.detailData.proxyName]
						this.proxyChilds[that.detailData.proxyName] = {}
						await that.$nextTick()
						that.nodeClick(res.data, this.commissionModel == 2 ? 2 : 1)
					}
				})
				.catch(() => {
					that.loading = false
				})
		},
		getProxyChildList(node, resolve) {
			this._proxyChildList(node, async (childList) => {
				resolve(childList)
				// console.log('____wait check :', node.data.userName, this.currentNodeData, this.proxyChilds)
				if (
					this.currentNodeData?.userName &&
					node.data.userName ===
						this.currentNodeData?.parentProxyName &&
					this.proxyChilds[(this.currentNodeData?.userName)]
				) {
					await this.$nextTick()
					if (this.currentNodeData?.type === 1) {
						this.setCurrentProxy(this.currentNodeData?.userName)
					} else if (this.currentNodeData?.type === 2) {
						const node = this.$refs.tree.getNode(
							this.currentNodeData?.userName
						)
						node && this.toggleMember(node)
					}
				}
			})
		},
		_proxyChildList(node, resolve) {
			// console.log('_____node child :', node)
			if (!node.data.userName) {
				resolve([])
				return
			}
			if (this.proxyChilds[node.data.userName]?.childList) {
				resolve(this.proxyChilds[node.data.userName].childList)
				return
			} else if (node.data.childList) {
				this.proxyChilds[node.data.userName] = {
					...node.data
				}

				for (const child of node.data.childList) {
					this.proxyChilds[child.userName] = {
						...child
					}
				}

				resolve(node.data.childList)
				return
			}
			// else if (!node.data.directlyUnderProxyNum) {
			// 	this.proxyChilds[node.data.userName] = {
			// 		...node.data,
			// 		childList: []
			// 	}
			// 	resolve([])
			// 	return
			// }
			const data = {
				id: node.data.id,
				merchantId: this.detailData.merchantId,
				reportDate: this.detailData.reportDate
			}
			data.createdAtStart = this.createdAtStart || undefined
			data.createdAtEnd = this.createdAtEnd || undefined

			this.$api
				.proxyLevelLink(data)
				.then((res) => {
					this.proxyChilds[node.data.userName] = {
						...node.data,
						childList: res.data?.childList || []
					}

					if (res.data?.childList) {
						for (const child of res.data?.childList) {
							this.proxyChilds[child.userName] = {
								...child
							}
						}
					}

					resolve(res.data?.childList)
				})
				.catch(() => {
					this.proxyChilds[node.data.userName] = {
						...node.data,
						childList: []
					}
					resolve([])
				})
		},
		async nodeExpend(data) {
			const index = this.expandedKeys.findIndex(
				(nodeUserName) => nodeUserName === data.userName
			)
			// console.log('nodeExpend :', data.userName, this.expandedKeys, index)
			if (index === -1) {
				this.expandedKeys.push(data.userName)
			}
		},
		nodeCollapse(data) {
			const index = this.expandedKeys.findIndex(
				(nodeUserName) => nodeUserName === data.userName
			)
			// console.log('nodeCollapse :', data, this.expandedKeys, index)
			if (index !== -1) {
				this.expandedKeys.splice(index, 1)
			}
		},
		async toggleMember(node) {
			const data = node.data
			// console.log('toggleMember :', data, this.proxyChilds[data.userName])
			if (this.proxyChilds?.[data.userName]?.memberList) {
				this.proxyChilds[data.userName].memberList.expand =
					this.currentNodeData?.type === 2
						? true
						: !this.proxyChilds[data.userName].memberList.expand

				node.setData({
					...node.data,
					childList: this.proxyChilds[data.userName].childList
				})
				await this.$nextTick()
				this.currentNodeData?.type === 2 && this.setCurrentMember()
				return
			}
			if (this.proxyChilds[data.userName] === undefined) {
				this.proxyChilds[data.userName] = {}
			}
			this.proxyChilds[data.userName].memberList = {
				loading: true,
				data: [],
				expand: true
			}
			node.loading = true
			node.setData({
				...node.data,
				childList: this.proxyChilds[data.userName].childList
			})

			this.$api
				.getAllMemberList({
					merchantId: node.data.merchantId,
					parentProxyId: node.data.id,
					reportDate: this.detailData.reportDate
				})
				.then(async (res) => {
					// console.log('res :', res)
					node.loading = false
					if (res?.data?.length) {
						this.proxyChilds[
							data.userName
						].memberList.data = res.data.map((item) => {
							return {
								parentProxyId: node.data.id,
								parentProxyName: node.data.userName,
								...item
							}
						})
					} else {
						this.proxyChilds[data.userName].memberList.data = []
					}
					this.proxyChilds[data.userName].memberList.loading = false

					node.setData({
						...node.data,
						childList: this.proxyChilds[data.userName].childList
					})
					await this.$nextTick()
					this.currentNodeData?.type === 2 && this.setCurrentMember()
				})
				.catch((e) => {
					node.loading = false
					this.proxyChilds[data.userName].memberList.loading = false
					node.setData({
						...node.data,
						childList: this.proxyChilds[data.userName].childList
					})
				})
		},
		cancelCurrentNode() {
			document
				.getElementsByClassName('tree-item is-current')?.[0]
				?.classList?.remove?.('is-current')
		},
		nodeClick(data, type) {
			// 是否更新选中数据
			const isUpdateSelect = !this.currentNodeData.userName
			this.currentNodeData = {}

			this.cancelCurrentNode()
			if (!data.userName) {
				return
			}
			let className = data.userName
			if (type === 1) {
				className += ' node-label'
			} else if (type === 2) {
				className += ' member-item'
			}
			document
				.getElementsByClassName(className)?.[0]
				?.classList?.add?.('is-current')

			if (isUpdateSelect) {
				this.$emit('update:selectedData', {
					...data,
					userName: data.userName,
					type: type
				})
			}
		},
		levelExpend(data) {
			return new Promise(async (resolve) => {
				if (!data?.length || !data[0].userName) {
					resolve({})
					return
				}

				if (data[0].childList) {
					//
					// this.currentNodeData.proxyLevel.push(data[0].userName)
					this.nodeExpend(data[0])
					const result = await this.levelExpend(data[0].childList)
					resolve(result)
				} else {
					// 记录当前代理信息，用于上级代理获取代理结构树后选中当前代理
					this.currentNodeData = {
						...data[0],
						proxyLevel: this.currentNodeData.proxyLevel || [],
						type: this.currentNodeData.type || 0,
						memberName: this.currentNodeData.memberName || ''
					}

					const node = this.$refs.tree.getNode(
						this.currentNodeData.userName
					)
					if (node) {
						if (this.currentNodeData.type === 1) {
							this.nodeClick(data[0], 1)
						} else if (this.currentNodeData.type === 2) {
							node && this.toggleMember(node)
						}
					}

					resolve(data[0])
				}
			})
		},
		async setCurrentProxy(proxyName) {
			this.cancelCurrentNode()
			if (!proxyName) {
				return
			} else if (this.proxyChilds[proxyName]) {
				this.currentNodeData.userName = proxyName
				this.currentNodeData.type = 1
				this.nodeClick(this.proxyChilds[proxyName], 1)
				return
			}

			this.currentNodeData = {
				type: 1,
				proxyLevels: []
			}

			try {
				const res = await this.$api.proxyLevelLinkByUserName({
					name: proxyName,
					nameType: 1
				})
				await this.levelExpend(res?.data)
			} catch (e) {
				console.error(e)
			}
		},
		async setCurrentMember(memberName) {
			this.cancelCurrentNode()
			if (!memberName) {
				const dom =
					this.currentNodeData?.type !== 2 ||
					!this.currentNodeData?.memberName
						? null
						: document.getElementsByClassName(
								'member-item ' + this.currentNodeData.memberName
						  )?.[0]

				// console.log('____setCurrentMember :', this.currentNodeData, dom)
				if (dom) {
					dom?.click?.()
				}
				return
			}

			this.currentNodeData = {
				type: 2,
				proxyLevels: [],
				memberName
			}

			try {
				const { data } = await this.$api.getOutlineInfo({
					userName: memberName,
					merchantId: this.detailData.merchantId
				})

				if (data?.parentProxyName) {
					const levelRes = await this.$api.proxyLevelLinkByUserName({
						name: data?.parentProxyName,
						nameType: 1
					})
					await this.levelExpend(levelRes?.data)
				}
			} catch (e) {
				console.error(e)
			}
		}
	}
}
</script>
<style lang="scss" scoped>
.proxy-tree {
	width: max-content;
	min-width: 100%;
	height: 100%;
	// ::v-deep .el-tree-node {
	// 	// padding-bottom: 4px;
	// 	// padding-top: 4px;
	// }
	::v-deep .el-icon-caret-right:before {
		// 未展开
		content: '\e6d9';
		font-size: 18px;
	}
	::v-deep .el-tree-node__expand-icon {
		cursor: pointer;
	}
	::v-deep .expanded:before,
	::v-deep .el-tree-node__expand-icon.is-leaf:before {
		// 展开
		content: '\e6d8';
		font-size: 18px;
	}
	::v-deep .expanded {
		// 展开不旋转
		-webkit-transform: rotate(0deg);
		transform: rotate(0deg);
	}
	::v-deep .el-tree-node__content {
		align-items: baseline;
		height: auto;
		background-color: transparent !important;
		cursor: default;
	}
	::v-deep .el-tree-node.is-current {
		background-color: transparent;
	}
}

.custom-tree-node {
	display: flex;
	align-items: baseline;
	position: relative;
	z-index: 1;
	.node-label {
		cursor: pointer;
	}
	.member-expand {
		margin-left: 10px;
		display: flex;
		flex-direction: column;
		.el-icon {
			font-size: 18px;
			cursor: pointer;
		}
	}
	.member-tree {
		.member-item {
			margin: 4px 30px;
			position: relative;
			cursor: pointer;
		}
		.member-item::before {
			content: ' ';
			height: 100%;
			width: 1px;
			position: absolute;
			left: -21px;
			top: 0px;
			border-width: 1px;
			border-left: 1px dashed #52627c;
		}
		.member-item:last-child::before {
			height: 50%;
		}
		.member-item::after {
			content: '';
			width: 20px;
			height: 20px;
			position: absolute;
			left: -21px;
			top: 50%;
			border-width: 1px;
			border-top: 1px dashed #52627c;
		}
	}
	.toggin-show {
		display: block;
	}
	.toggin-hide {
		display: none;
	}
}
</style>
<style lang="scss">
// .proxy-tree .el-tree-node.is-current > .el-tree-node__content .node-label,
.proxy-tree .tree-item.is-current {
	background-color: #caf982;
	font-weight: bold;
}
// .proxy-tree .el-tree-node__content {
// 	position: relative;
// 	&::before {
// 		content: ' ';
// 		// position: absolute;
// 		// top: 50%;
// 		// left: $indent/2;
// 		width: 20px;
// 	    height: 38px;
// 	    border-bottom: 1px dotted #999;
// 	    align-self: flex-start;
// 	    border-left: 1px dotted;
// 	    margin-top: -23px;
// 	}
// }
.proxy-tree {
	.el-tree-node {
		position: relative;
		padding-left: 16px;
	}
	// .el-tree-node__content {
	// 	margin-top: 10px;
	// }
	.el-tree-node__children {
		padding-left: 16px;
	}
	.el-tree-node::before {
		content: '';
		height: 100%;
		width: 1px;
		position: absolute;
		left: -1px;
		top: 15px;
		border-width: 1px;
		border-left: 1px dashed #52627c;
	}
	.el-tree-node:last-child::before {
		// height: 38px;
		display: none;
	}
	.el-tree-node::after {
		content: '';
		width: 24px;
		height: 20px;
		position: absolute;
		left: -1px;
		top: 15px;
		border-width: 1px;
		border-top: 1px dashed #52627c;
	}
	& > .el-tree-node::after {
		border-top: none;
	}
	& > .el-tree-node::before {
		border-left: none;
	}
	.el-tree-node__expand-icon {
		font-size: 18px;
		color: #000;
		&.is-leaf {
			color: transparent;
			// display: none;
		}
	}
	.el-tree-node.is-expanded > .el-tree-node__content {
		position: relative;
	}
	.el-tree-node.is-expanded > .el-tree-node__content::before {
		content: '';
		height: 100%;
		width: 1px;
		position: absolute;
		left: 15px;
		top: 15px;
		border-width: 1px;
		border-left: 1px dashed #52627c;
	}
	.el-tree-node.is-expanded > .el-tree-node__children:empty::after {
		content: '';
		height: 100%;
		width: 30px;
		position: absolute;
		left: 15px;
		top: 15px;
		border-width: 1px;
		background: #fff;
	}
	.el-tree-node__expand-icon.is-leaf {
		z-index: 1;
		color: inherit;
	}
}
</style>
